import java.util.StringTokenizer;
import java.util.Stack;
public class OutOfStack {
    private final char ADD = '+';
    private final char SUBTRACT = '-';
    private final char MULTIPLY = '*';
    private final char DIVIDE1 = '÷';
    private final char DIVIDE2 = '/';
    private Stack stack;//存放操作数的栈

    public OutOfStack() {
        stack = new Stack();
    }

    public Rational evaluate(String expr) {
        Rational op1 = new Rational();
        Rational op2 = new Rational();
        Rational result = new Rational();
        result.setNumerator(0);
        String token;
        StringTokenizer tokenizer = new StringTokenizer(expr);//划分表达式

        while (tokenizer.hasMoreTokens()) {
            token = tokenizer.nextToken();//将算数表达式进行分解

            if (isOperator(token))//遇到操作符，弹出栈顶的两个数进行运算
            {
                op2 = (Rational) stack.pop();
                op1 = (Rational) stack.pop();//弹出最上面两个操作数
                result = evalSingleOp(token.charAt(0), op1, op2);//根据运算符进行运算
                stack.push(result);//将计算结果压栈
            } else {
                Rational num = new Rational();
                num.setNumerator(Integer.parseInt(token));//将操作数由string转变为Rational
                stack.push(num);//操作数入栈
            }
        }

        return result;//输出结果
    }

    private boolean isOperator(String token)//判断是否为运算符
    {
        return (token.equals("+") || token.equals("-") ||
                token.equals("*") || token.equals("÷") || token.equals("/"));
    }

    private Rational evalSingleOp(char operation, Rational op1, Rational op2) {
        Rational result = new Rational();
        result.setNumerator(0);
        switch (operation) {
            case ADD:
                result = op1.add(op2);
                break;
            case SUBTRACT:
                result = op1.sub(op2);
                break;
            case MULTIPLY:
                result = op1.muti(op2);
                break;
            case DIVIDE1:
            case DIVIDE2:
                result = op1.div(op2);
                break;
            default:
                System.out.println("Error!");
        }
        return result;
    }
}


